package mongopkg

import (
	"context"
	"errors"
	"fmt"
	"gitee.com/wanjimao/dongli-kit/pkg/setting"
	"go.mongodb.org/mongo-driver/mongo"
	"go.mongodb.org/mongo-driver/mongo/options"
	"go.mongodb.org/mongo-driver/mongo/readpref"
	"go.uber.org/fx"
	"go.uber.org/zap"
	"net/url"
	"os"
	"time"
)

type Param struct {
	fx.In
	MongoDb *mongo.Client `name:"MongoDb"`
}

type Result struct {
	fx.Out
	MongoDb *mongo.Client `name:"MongoDb"`
}

func (f *Result) Execute(MongoDbService) {
	documentStoreUrl := os.Getenv("DOCUMENT_STORE_URL")
	if u, e := url.Parse(documentStoreUrl); e != nil {
		err := e
		fmt.Sprintf(err.Error())
		panic(err)
	} else {
		switch u.Scheme {
		case "mongodb":
			username := u.User.Username()
			if username == "" {
				username = "默认账号"
			}

			password, set := u.User.Password()
			if !set {
				password = "默认密码"
			}
			type ClusterConfig struct {
				ConnUrl  string `default:"mongo_db://localhost:27017"`
				Username string
				Password string
			}
			cfg := ClusterConfig{
				ConnUrl:  fmt.Sprintf("mongodb://%s", u.Host),
				Username: username,
				Password: password,
			}
			ctx, cancel := context.WithTimeout(context.Background(), 30*time.Second)
			defer cancel()
			credential := options.Credential{
				Username: username,
				Password: password,
			}
			if client, err := mongo.Connect(
				ctx,
				options.Client().ApplyURI(cfg.ConnUrl).SetAuth(credential),
			); err != nil {
				panic(err)
			} else {
				err = client.Ping(ctx, readpref.Primary())
				if err != nil {
					panic(err)
				}
				f.MongoDb = client
			}
		default:
			panic(errors.New("启动失败"))
		}
	}
}

var Module = fx.Module("mongopkg", fx.Provide(
	func(
		l *zap.Logger,
		s setting.Param,
		//cService curlservice.Param,
	) (out Result, err error) {
		if svc, e := NewMongoDb(
			l,
			s,
			//cService.CurlService,
		); e != nil {
			err = e
		} else {
			out.Execute(svc)
		}
		return
	},
),
)
